package proto

import (
	"fmt"
	"io/ioutil"
	"regexp"
	"strconv"
	"strings"
	D "websocket_apn/define"

	"github.com/gorilla/websocket"
)

func paraseTxt(file string) []D.Message {
	// 读取文件内容到字符串
	content, err := ioutil.ReadFile(file)
	if err != nil {
		fmt.Println("读取文件错误:", err)
		return []D.Message{}
	}
	return ParaFiddlerStrToMsg(content)
}

func ParaFiddlerStrToMsg(content []byte) []D.Message {
	// 正则表达式匹配所有结果
	re := regexp.MustCompile(`WebSocket'WebSocket #(\d+)'\s+MessageID:\s+(\w+)\.(\d+)\s+MessageType:\s+(\w+)\s+PayloadString:\s+([\w\d-]+)\s+Masking:\s+([<>a-zA-Z0-9-]+)`)
	matches := re.FindAllStringSubmatch(string(content), -1)

	// 解析每个匹配的结果到结构体中
	var messages []D.Message
	for _, match := range matches {
		if len(match) != 7 {
			fmt.Println("匹配结果长度错误:", match)
			continue
		}

		// 提取匹配的各个部分
		sessionIDStr := match[1]
		messageIDType := match[2]
		msgIDNum := match[3]
		messageType := match[4]
		payloadString := match[5]
		masking := match[6]

		// 解析会话 ID
		sessionID, err := strconv.Atoi(sessionIDStr)
		if err != nil {
			fmt.Println("解析会话 ID 错误:", err)
			continue
		}

		// 解析消息 ID
		messageIDNum, err := strconv.Atoi(msgIDNum)
		if err != nil {
			fmt.Println("解析消息 ID 错误:", err)
			continue
		}

		// 解析 PayloadBytes
		payloadBytes := parsePayloadString(payloadString)

		// 创建 Message 结构体并添加到 messages 切片中
		message := D.Message{
			SessionID:     sessionID,
			MessageIDType: messageIDType,
			MessageIDNum:  messageIDNum,
			PayloadBytes:  payloadBytes,
			Masking:       masking,
		}
		if messageType == "Binary" {
			message.MessageType = websocket.BinaryMessage
		} else if messageType == "PingMessage" {
			message.MessageType = websocket.PingMessage
		}
		messages = append(messages, message)
	}
	return messages
}

// 解析 PayloadString 字符串为 []byte
func parsePayloadString(payloadString string) []byte {
	bytesStr := strings.Split(payloadString, "-")
	var bytes []byte
	for _, bStr := range bytesStr {
		b, err := strconv.ParseUint(bStr, 16, 8)
		if err != nil {
			continue
		}
		bytes = append(bytes, byte(b))
	}
	return bytes
}
